package com.daily.daily_push.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.daily.daily_push.service.K8sApiService;
import com.daily.daily_push.utils.K8sConstantsUtil;
import io.kubernetes.client.custom.NodeMetrics;
import io.kubernetes.client.custom.NodeMetricsList;
import io.kubernetes.client.custom.Quantity;
import io.kubernetes.client.openapi.ApiClient;
import io.kubernetes.client.openapi.ApiException;
import io.kubernetes.client.openapi.Configuration;
import io.kubernetes.client.openapi.apis.AppsV1Api;
import io.kubernetes.client.openapi.apis.CoreV1Api;
import io.kubernetes.client.openapi.models.*;
import io.kubernetes.client.util.Yaml;
import io.kubernetes.client.util.generic.GenericKubernetesApi;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import java.io.File;
import java.io.IOException;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Slf4j
@Service
public class K8SApiServiceImpl implements K8sApiService {


    @Override
    public List<V1Pod> k8sGetPods(ApiClient client,String namespace, String pretty, Boolean allowWatchBookmarks, String _continue, String fieldSelector, String labelSelector, Integer limit, String resourceVersion, String resourceVersionMatch, Integer timeoutSeconds, Boolean watch) {

        try {
            Configuration.setDefaultApiClient(client);
            CoreV1Api coreV1Api = new CoreV1Api();
            V1PodList v1PodList = coreV1Api.listNamespacedPod("default", "true", null, null, null, null, null, null, null, null, null);
            return v1PodList.getItems();
        } catch (ApiException e) {
            log.error("获取pod列表失败： {}", e.getResponseBody());
            e.printStackTrace();
            return null;
        }
    }

    @Override
    public String getNamespacedPodLog(ApiClient client,String podName, String namespace, String container, Boolean follow, Boolean insecureSkipTLSVerifyBackend, Integer limitBytes, String pretty, Boolean previous, Integer sinceSeconds, Integer tailLines, Boolean timestamps) {

        try {
            Configuration.setDefaultApiClient(client);
            CoreV1Api coreV1Api = new CoreV1Api();
            return coreV1Api.readNamespacedPodLog(podName, namespace, container, null, null, null, null, null, null, null, null);
        } catch (ApiException e) {
            log.error("获取pod日志失败： {}", e.getResponseBody());
            e.printStackTrace();
        }
        return null;
    }

    @Override
    public V1Pod createNamespacePod(ApiClient client,String podName, String container, String image, Integer containerPort, String namespace, String pretty, String dryRun, String fieldManager, String fieldValidation) {
        try {
            Configuration.setDefaultApiClient(client);
            CoreV1Api coreV1Api = new CoreV1Api();
            V1Pod pod = new V1Pod()
                    .metadata(new V1ObjectMeta().name(podName))
                    .spec(new V1PodSpec()
                            .containers(Arrays.asList(
                                    new V1Container()
                                            .name(container)
                                            .image(image)
                                            .ports(Arrays.asList(
                                                    new V1ContainerPort().containerPort(containerPort)
                                            ))
                            ))
                    );

            V1Pod createdPod = coreV1Api.createNamespacedPod(namespace, pod, pretty, dryRun, fieldManager, fieldValidation);
            return createdPod;
        } catch (ApiException e) {
            log.error("创建pod失败： {}", e.getResponseBody());
            e.printStackTrace();
            return null;
        }
    }

    @Override
    public V1Deployment createDeploymentPod(ApiClient client,File yamlFile, String namespace, String pretty, String dryRun, String fieldManager, String fieldValidation) {
        Configuration.setDefaultApiClient(client);
        AppsV1Api appsV1Api = new AppsV1Api();
        V1Deployment pod1 = null;
        try {
            pod1 = (V1Deployment) Yaml.load(yamlFile);
        } catch (IOException e) {
            log.error("创建pod失败： {}", e.getMessage());
            e.printStackTrace();
        }
        try {
            return appsV1Api.createNamespacedDeployment("default", pod1, "true", null, null, null);
        } catch (ApiException e) {
            log.error("创建pod失败： {}", e.getResponseBody());
            e.printStackTrace();
            return null;
        }
    }

    @Override
    public List<V1Deployment> listNamespacedDeployment(ApiClient client,String namespace, String pretty, Boolean allowWatchBookmarks, String _continue, String fieldSelector, String labelSelector, Integer limit, String resourceVersion, String resourceVersionMatch, Integer timeoutSeconds, Boolean watch) {

        try {
            Configuration.setDefaultApiClient(client);
            AppsV1Api appsV1Api = new AppsV1Api();
            V1DeploymentList v1DeploymentList = appsV1Api.listNamespacedDeployment(namespace, pretty, null, null, null, null, null, null, null, null, null);
            return v1DeploymentList.getItems();
        } catch (ApiException e) {
            log.error("查询Deployment列表失败： {}", e.getResponseBody());
            e.printStackTrace();
            return null;
        }
    }

    @Override
    public Map<String, Object> k8sInfo(ApiClient client) {

        try {
            Configuration.setDefaultApiClient(client);
            CoreV1Api coreV1Api = new CoreV1Api();
            int nodeCount = 0;
            int totalCpu = 0;
            Long totalMemory = 0L;

            V1NodeList list6 = coreV1Api.listNode("true", null, null, null, null, null, null, null, null, null);
            for (V1Node item : list6.getItems()) {
                nodeCount++;
                Map<String, Quantity> allocatable = item.getStatus().getAllocatable();
                totalCpu += Integer.parseInt(allocatable.get("cpu").getNumber().toString());
                totalMemory += Long.parseLong(allocatable.get("memory").getNumber().toString());
            }

            HashMap<String, Object> hashMap = new HashMap<>();
//        节点总数
            hashMap.put("nodeCount", nodeCount);
//        总CPU
            hashMap.put("totalCpu", totalCpu);
//        总内存
            hashMap.put("totalMemory", totalMemory);

            return hashMap;
        } catch (ApiException e) {
            log.error("查询查询k8s集群信息失败： {}", e.getResponseBody());
            e.printStackTrace();
            return null;
        }
    }

    @Override
    public List<V1Namespace> listNamespace(ApiClient client) {

        try {
            Configuration.setDefaultApiClient(client);
            CoreV1Api coreV1Api = new CoreV1Api();
            V1NamespaceList listNamespace = coreV1Api.listNamespace("true", null, null, null, null, null, null, null, null, null);
            return listNamespace.getItems();
        } catch (ApiException e) {
            log.error("查询k8s命名空间列表信息失败： {}", e.getResponseBody());
            e.printStackTrace();
            return null;
        }
    }

    @Override
    public V1ConfigMap listConfigMap(ApiClient client,String namespace, String configMapName) {
        try {
            Configuration.setDefaultApiClient(client);
            CoreV1Api coreV1Api = new CoreV1Api();
            V1ConfigMap configMap = coreV1Api.readNamespacedConfigMap(configMapName, namespace, "true");
            return configMap;
        } catch (ApiException e) {
            log.error("查询k8s命名空间下的configMap信息失败： {}", e.getResponseBody());
            e.printStackTrace();

            return null;
        }
    }

    @Override
    public Map listSecret(ApiClient client,String namespace, String secretName) {
        try {
            Configuration.setDefaultApiClient(client);
            CoreV1Api coreV1Api = new CoreV1Api();
            V1Secret secret =coreV1Api.readNamespacedSecret(secretName, namespace, null);
            HashMap<String, Object> map = new HashMap<>();
            secret.getData().forEach((key, value) -> {
                String decodedValue = new String(java.util.Base64.getDecoder().decode(value));
                map.put(key,decodedValue);
            });
            return map;
        } catch (ApiException e) {
            log.error("查询k8s命名空间下的secret信息失败： {}", e.getResponseBody());
            e.printStackTrace();
            return null;
        }
    }
}
